using AutoMapper;
using B.S.NewMedical.Api.Write.Application.Command.ContentManagement.Department;
using B.S.NewMedical.Domain.Doctor;
using B.S.NewMedical.Infrastructure.Interface;
using MediatR;
using System;
using System.Linq;
using System.Threading;
using System.Threading.Tasks;

namespace B.S.NewMedical.Api.Write.Application.Handler.ContentManagement.Department
{
    /// <summary>
    /// 更新科室命令处理器
    /// </summary>
    public class UpdateDepartmentCommandHandler : IRequestHandler<UpdateDepartmentCommand, bool>
    {
        private readonly IMapper _mapper;
        private readonly IBaseRepository<DepartmentModel> _departmentRepository;

        public UpdateDepartmentCommandHandler(IMapper mapper, IBaseRepository<DepartmentModel> departmentRepository)
        {
            _mapper = mapper ?? throw new ArgumentNullException(nameof(mapper));
            _departmentRepository = departmentRepository ?? throw new ArgumentNullException(nameof(departmentRepository));
        }

        /// <summary>
        /// 处理更新科室命令
        /// </summary>
        /// <param name="request">更新科室命令</param>
        /// <param name="cancellationToken">取消令牌</param>
        /// <returns>是否更新成功</returns>
        public async Task<bool> Handle(UpdateDepartmentCommand request, CancellationToken cancellationToken)
        {
            // 查找要更新的科室
            var existingDepartment = await _departmentRepository.GetValue(request.Id);
            if (existingDepartment == null || existingDepartment.IsDeleted)
            {
                return false;
            }

            // 如果要修改为二级科室，验证父级科室是否存在
            if (request.ParetId > 0)
            {
                var parentDepartment = await _departmentRepository.GetValue(request.ParetId);
                if (parentDepartment == null || parentDepartment.IsDeleted)
                {
                    throw new ArgumentException("父级科室不存在或已被删除");
                }

                // 验证父级科室确实是一级科室
                if (parentDepartment.ParetId != 0)
                {
                    throw new ArgumentException("只能设置一级科室作为父级科室");
                }

                // 防止将科室设置为自己的下级
                if (request.ParetId == request.Id)
                {
                    throw new ArgumentException("不能将科室设置为自己的下级");
                }
            }

            // 如果当前科室有下级科室，不允许修改为二级科室
            if (request.ParetId > 0 && existingDepartment.ParetId == 0)
            {
                var hasSubDepartments = _departmentRepository.GetAll()
                    .Any(d => d.ParetId == request.Id && !d.IsDeleted);

                if (hasSubDepartments)
                {
                    throw new ArgumentException("该科室有下级科室，不能修改为二级科室");
                }
            }

            // 检查科室名称是否重复（同一父级下不能有相同名称的科室，排除自己）
            var duplicateCheck = _departmentRepository.GetAll()
                .Where(d => d.ParetId == request.ParetId && 
                           d.DepartmentName == request.DepartmentName && 
                           d.Id != request.Id &&
                           !d.IsDeleted)
                .ToList();

            if (duplicateCheck.Any())
            {
                throw new ArgumentException($"在{(request.ParetId == 0 ? "一级科室" : "该父级科室")}下已存在名称为'{request.DepartmentName}'的科室");
            }

            // 使用 AutoMapper 将命令映射到现有实体
            _mapper.Map(request, existingDepartment);

            // 设置更新时间
            existingDepartment.UpdateTime = DateTime.Now;

            // 调用仓储层更新数据
            await _departmentRepository.UpdateAsync(existingDepartment);
            return true;
        }
    }
}